#!/usr/bin env python
# -*- coding: utf-8 -*-
###########################################################################
#   Copyright (C) 2008 by Serj Poltavsky                                  #
#   serge.uliss at gmail.com                                              #
#                                                                         #
#   This program is free software; you can redistribute it and/or modify  #
#   it under the terms of the GNU General Public License as published by  #
#   the Free Software Foundation; either version 3 of the License, or     #
#   (at your option) any later version.                                   #
#                                                                         #
#   This program is distributed in the hope that it will be useful,       #
#   but WITHOUT ANY WARRANTY; without even the implied warranty of        #
#   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the         #
#   GNU General Public License for more details.                          #
#                                                                         #
#   You should have received a copy of the GNU General Public License     #
#   along with this program. If not, see <http://www.gnu.org/licenses/>   #
###########################################################################

import sys
import subprocess
from convert import *

class VideoMencoder(Convert):
    def __init__(self, src, dest, format, aspect):
        Convert.__init__(self, src, dest)
        self.init_options()
        self.init_codec()
        self.format = format
        self.aspect = aspect
        self.copyaudio = False

    def convert(self):
        cmd = self.make_cmd()
        if __debug__:
            print >>sys.stderr, "Encoding video..."
            print >>sys.stderr, " ".join(cmd)

        try:
            ret = subprocess.call(cmd, stderr=subprocess.PIPE, stdout=subprocess.PIPE)
            if ret != 0:
                print >>sys.stderr, "Encoding faild with code %i" % (ret)
        except OSError, e:
            print >>sys.stderr, "Encoding execution failed:", e

    def get_aspect(self):
        return self.__aspect

    def get_copyaudio(self):
        return self.__copyaudio

    def get_format(self):
        return self.__format

    def init_codec(self):
        self.__codec_options = {}
        self.__codec_options['vcodec'] = 'mpeg2video'
        self.__codec_options['vrc_buf_size'] = 1835
        self.__codec_options['vrc_maxrate'] = 9800
        self.__codec_options['vbitrate'] = 5000
        self.__codec_options['keyint'] = 15
        self.__codec_options['vstrict'] = 0

    def init_options(self):
        self.__options = {}
        self.__options['-ovc'] = 'lavc'
        self.__options['-of'] = 'mpeg'
        self.__options['-mpegopts'] = 'format=dvd:tsaf'

    def is_converted(self):
        return self.is_dest_exists() and not self.is_dest_older()

    def make_cmd(self):
        cmd = []
        if sys.platform=='win32':
            cmd.append('mencoder.exe')
        else:
            cmd.append('mencoder')
        lavcopts = []
        for k, v in self.__codec_options.items():
            s = k
            if v: s += '=' + str(v)
            lavcopts.append(s)
        self.__options['-lavcopts'] = ':'.join(lavcopts)
        cmd.extend([k + " " + str(v) for k, v in self.__options.items()])
        cmd.extend(['-o', self.src])
        cmd.append(self.dest)
        return cmd

    def set_aspect(self, aspect):
        if aspect in ((4,3), (16,9)):
            self.__aspect = aspect
            self.__codec_options['aspect'] = '/'.join([str(x) for x in aspect])
        else:
            raise RuntimeError('Wrong aspect given: %s' % str(aspect))

    def set_codec_options_hq(self):
        self.__codec_options['vbitrate'] = 8000
        self.__codec_options['trell'] = ''
        self.__codec_options['mbd'] = 2
        self.__codec_options['precmp'] = 2
        self.__codec_options['subcmp'] = 2
        self.__codec_options['cmp'] = 2
        self.__codec_options['dia'] = -10
        self.__codec_options['predia'] = -10
        self.__codec_options['cbp'] = ''
        self.__codec_options['mv0'] = ''
        self.__codec_options['vqmin'] = 1
        self.__codec_options['lmin'] = 1
        self.__codec_options['dc'] = 10

    def set_codec_options_lq(self):
        reset = ('dc', 'lmin', 'vqmin', 'mv0', 'cbp', 'predia', 'dia', 'cmp', 'subcmp', 'precmp', 'mbd','trell')
        for k in self.__codec_options.keys():
            if k in reset:
                del self.__codec_options[k]
        self.__codec_options['vbitrate'] = 5000

    def set_copyaudio(self, copyaudio):
        self.__copyaudio = bool(copyaudio)
        if self.__copyaudio:
            self.__options['-oac'] = 'copy'
            for k in self.__options.keys():
                if k in ('-srate', '-af'):
                    del self.__options[k]
            for k in self.__codec_options.keys():
                if k in ('acodec', 'abitrate'):
                    del self.__codec_options[k]
        else:
            self.__options['-oac'] = 'lavc'
            self.__options['-srate'] = 48000
            self.__options['-af'] = 'lavcresample=48000'
            self.__codec_options['acodec'] = 'ac3'
            self.__codec_options['abitrate'] = 192

    def set_format(self, format):
        if format in ('pal', 'ntsc'):
            self.__format = format
            if self.format == 'pal':
                self.__options['-ofps'] = 25
                self.__options['-vf'] = 'scale=720:576,harddup'
            else:
                self.__options['-ofps'] = '30000/1001'
                self.__options['-vf'] = 'scale=720:480,harddup'
        else:
            raise RuntimeError('Wrong video format given: %s', format)

    aspect = property(get_aspect, set_aspect)
    copyaudio = property(get_copyaudio, set_copyaudio)
    format = property(get_format, set_format)